import {
  ipcMain,
  dialog,
  app,
  BrowserWindow
} from 'electron'
import Server from '../server/index'
import cardUtils from '../services/cardUtils'
import cardMT625Utils from '../services/cardUtilsMT625'
import barUtils from '../services/barUtils'
import mqtt from '../services/mqtt'
import {
  winURL
} from '../config/StaticPath'
import downloadFile from './downloadFile'
import Update from './checkupdate'
import path from 'path'
import {
  GSAConstants
} from './com'


export default {
  Mainfunc (mainWindow, IsUseSysTitle) {
    var proxy_dll_win32 = null
    var proxy_dll_625_win32 = null
    var proxy_bar_dll_win32 = null
    var proxy_weight_dll_win32 = null
    const updater = new Update()


    let fs = require('fs')
    let url
    try {
      fs.readFile(
        path.join("C:\\nGSA\\", 'data.json'),
        'utf8',
        (err, data) => {
          if (err) {
            console.log(err)
          } else {
            url = JSON.parse(data).updateUrl
            if (url) {
              updater.setFeedURL(url)
            }
          }
        }
      )
    } catch {
      dialog.showErrorBox("请检查", "C:\\nGSA\\", 'data.json', '： 文件读取失败：找不到文件或文件格式有问题.')
      return
    }

    // 关闭资源
    app.on('before-quit', () => {
      cardUtils.exit(proxy_dll_win32)
      cardMT625Utils.exit(proxy_dll_625_win32)
    })
    // let fs = require('electron').remote.require('fs')
    updater.start()
    // handle是用来被pcRenderer.invoke调用的
    ipcMain.handle('IsUseSysTitle', async () => {
      return IsUseSysTitle
    })
    ipcMain.handle('windows-mini', (event, args) => {
      BrowserWindow.fromWebContents(event.sender)?.minimize()
    })
    ipcMain.handle('window-max', async (event, args) => {
      if (BrowserWindow.fromWebContents(event.sender)?.isMaximized()) {
        BrowserWindow.fromWebContents(event.sender)?.unmaximize()
        return {
          status: false
        }
      } else {
        BrowserWindow.fromWebContents(event.sender)?.maximize()
        return {
          status: true
        }
      }
    })
    ipcMain.handle('window-close', (event, args) => {
      BrowserWindow.fromWebContents(event.sender)?.close()
    })
    ipcMain.handle('start-download', (event, msg) => {
      downloadFile.download(
        BrowserWindow.fromWebContents(event.sender),
        msg.downloadUrL
      )
    })

    ipcMain.handle('check-update', () => {
      console.log('ipcMain.js checkUpdate')

      updater.checkUpdate(mainWindow)
    })
    ipcMain.handle('confirm-update', () => {
      updater.quitInstall()
    })
    ipcMain.handle('open-messagebox', async (event, arg) => {
      const res = await dialog.showMessageBox(
        BrowserWindow.fromWebContents(event.sender), {
        type: arg.type || 'info',
        title: arg.title || '',
        buttons: arg.buttons || [],
        message: arg.message || '',
        noLink: arg.noLink || true,
      }
      )
      return res
    })
    ipcMain.handle('open-errorbox', (event, arg) => {
      dialog.showErrorBox(arg.title, arg.message)
    })

    ipcMain.on('isUpdateNow', (e, arg) => {
      //console.log("开始更新");
      //some code here to handle event
      //重点是以下几行代码，顺序不要乱
      mainWindow.webContents.send('quit');
      autoUpdater.quitAndInstall();
      if (mainWindow && mainWindow.destroy) {
        mainWindow.destroy();
      }
      app.quit();
    });

    ipcMain.handle('start-server', async () => {
      try {
        const serveStatus = await Server.StartServer()
        console.log(serveStatus)
        return serveStatus
      } catch (error) {
        dialog.showErrorBox('错误', error)
      }
    })
    ipcMain.handle('stop-server', async (event, arg) => {
      try {
        const serveStatus = await Server.StopServer()
        return serveStatus
      } catch (error) {
        dialog.showErrorBox('错误', error)
      }
    })

    // 加载DLL
    ipcMain.on('load-card-dll-thread', (event, arg) => {
      console.log('========加载DLL======')
      proxy_dll_win32 = cardUtils.init32Dll()
      event.reply('load-card-dll-thread-reply', 'DLL加载成功')
    })
    // 加载DLL
    ipcMain.on('load-weight-dll-thread', (event, arg) => {
      console.log('========加载DLL======')
      proxy_weight_dll_win32 = cardUtils.init32MeterInterfaceDll()
      event.reply('load-weight-dll-thread-reply', 'DLL加载成功')
    })

    // 打开文件夹
    ipcMain.on('open-dir-check-dialog', (event, arg) => {
      console.log('open-dir-check-dialog')
      dialog.showOpenDialog({
        properties: ['openDirectory']
      }).then(res => {
        console.log('open-dir-check-dialog-res', res)
        if (!res.canceled) {
          event.reply('open-dir-check-dialog-reply', res.filePaths[0])
        }
      })

    })

    // 称重
    ipcMain.on('read-weight', (event, arg) => {
      console.log('========read-weight======')
      if (!proxy_weight_dll_win32) {
        proxy_weight_dll_win32 = cardUtils.init32MeterInterfaceDll()
      }

      var resultObject = cardUtils.readWeightBridge(proxy_weight_dll_win32, arg)
      event.reply('read-weight-reply', resultObject)
    })
    // 称重
    ipcMain.on('reset-weight', (event, arg) => {
      console.log('========read-weight======')
      if (!proxy_weight_dll_win32) {
        proxy_weight_dll_win32 = cardUtils.init32MeterInterfaceDll()
      }

      var resultObject = cardUtils.resetWeightBridge(proxy_weight_dll_win32, arg)
      event.reply('reset-weight-reply', resultObject)
    })
    //读ID卡
    ipcMain.on('read-id-card', (event, arg) => {
      console.log('========read-id-card======')
      if (!proxy_dll_win32) {
        proxy_dll_win32 = cardUtils.init32Dll()
      }

      let resultObject;
      for (let index = 0; index < 1; index++) {
        resultObject = cardUtils.readerIDCardInfo(proxy_dll_win32)
        if (resultObject.readCode !== -777 && resultObject.readCode !== -401) {
          break
        }
      }
      if (resultObject.readCode === 0) {
        console.log(resultObject)
      }
      event.reply('read-id-card-reply', resultObject)
    })

    ipcMain.on('init-com', (event, port, read_mode) => {
      if (read_mode === 'MT-625') {
        if (proxy_dll_625_win32) {
          return;
        }
        proxy_dll_625_win32 = cardMT625Utils.init32Dll()
        event.reply('init-com-reply', {
          code: cardMT625Utils.initCom(proxy_dll_625_win32, port),
          com_port: port
        })
      }
    })
    //读PCC卡线程
    var readIcCode = -777
    var readIcPort = 0
    var readSuccessPort = 0
    ipcMain.on('read-ic-card', (event, port, read_mode, no_halt) => {
      console.log('========read-ic-card======')
      // 拔掉设备, 会导致 readIcPort 增加1， 然后永远连不上， 这里重置一下

      if (port) {
        readIcPort = port
      }
      let resultObject;
      if (read_mode === 'RF-200' || read_mode === 'RF-35LT') {
        if (!proxy_dll_win32) {
          proxy_dll_win32 = cardUtils.init32Dll()
        }

        if (no_halt == undefined || no_halt !== 1) {
          no_halt = 0;
        }

        for (let index = 0; index < 1; index++) {
          resultObject = cardUtils.readerICCardInfo(readIcPort, proxy_dll_win32, no_halt)
          if (resultObject.readCode !== -777 && resultObject.readCode !== -401) {
            break
          }
        }

        console.log('======返回代码:======' + readIcCode)
        console.log('======有效设备端口号:======' + resultObject)
        event.reply('read-ic-card-reply', resultObject)
        return;
      } else if (read_mode === 'MT-625' || true) {
        if (!proxy_dll_625_win32) {
          return;
        }
        event.reply('read-ic-card-reply', cardMT625Utils.readerICCardInfo(proxy_dll_625_win32, port, no_halt))
        return;
      }

      event.reply('read-ic-card-reply', {
        msg: '不支持的IC读卡器类型',
        readCode: -999
      })
    })

    ipcMain.on('write-card', (event, read_mode, msg, port) => {
      console.log('write-card', read_mode)

      if (read_mode === 'RF-200' || read_mode === 'RF-35LT') {
        if (!proxy_dll_win32) {
          proxy_dll_win32 = cardUtils.init32Dll()
        }

        // readIcPort = readSuccessPort
        let com = port;
        const p8 = msg.p8
        const p9 = msg.p9

        // com mode block  chData
        var resultObject = cardUtils.writeCard(proxy_dll_win32, com, p8, p9)
        // 如果返回的是设备找不到 且  端口号小于3 尝试在读一次
        // while (com < 3 && resultObject.readCode === -777) {
        // com += 1
        // resultObject = cardUtils.writeCard(proxy_dll_win32, com, p8, p9)
        // }
        event.reply('write-card-reply', resultObject)
      } else if (read_mode === 'MT-625' || true) {
        if (!proxy_dll_625_win32) {
          return;
        }

        let com = port;
        const p8 = msg.p8
        const p9 = msg.p9

        // com mode block  chData
        var resultObject = cardMT625Utils.writeCard(proxy_dll_625_win32, com, p8, p9)
        event.reply('write-card-reply', resultObject)
      }
    })

    ipcMain.on('read-card', (event, msg, read_mode, port) => {
      if (read_mode === 'RF-200' || read_mode === 'RF-35LT') {
        if (!proxy_dll_win32) {
          proxy_dll_win32 = cardUtils.init32Dll()
        }

        // readIcPort = readSuccessPort
        let com = port
        // com mode block  chData
        var resultObject = cardUtils.readCard(proxy_dll_win32, port - 1)
        // // 如果返回的是设备找不到 且  端口号小于3 尝试在读一次
        //while (com < 3 && resultObject.readCode === -777) {
        //  com += 1
        //  resultObject = cardUtils.readCard(proxy_dll_win32, com)
        //}

        event.reply('read-card-reply', resultObject)
      } else if (read_mode === 'MT-625' || true) {
        if (!proxy_dll_625_win32) {
          return;
        }
        var resultObject = cardMT625Utils.readCard(proxy_dll_625_win32, port - 1)
        event.reply('read-card-reply', resultObject)
      }
    })

    ipcMain.on('connect-bar', (event, msg) => {
      proxy_bar_dll_win32 = barUtils.initDll()
      console.log('connect-bar')

      const res = barUtils.connectBar(proxy_bar_dll_win32)
      // 开始检测状态
      setInterval(() => {
        barUtils.checkConnect(proxy_bar_dll_win32)
      }, 60000)
    })
    ipcMain.on('raise-bar', (event, msg) => {
      // 抬杆
      event.reply('raise-bar-reply', barUtils.raise(proxy_bar_dll_win32))
    })

    // 读取配置文件
    ipcMain.on('read-app-config', async (event, arg) => {
      console.log('=======读取配置文件=======' + arg)
      //  读取文件
      var result = {
        success: false,
        data: '',
        error: ''
      }
      try {
        fs.readFile(
          path.join("C:\\nGSA\\", 'data.json'),
          'utf8',
          (err, data) => {
            if (err) {
              console.log(err)
              result.success = false
              result.data = '文件读取失败：找不到文件或文件格式有问题.'
              result.error = err
            } else {
              result.success = true
              result.data = data
            }
            event.reply('read-app-config-reply', result)
          }
        )
      } catch (e) {
        result.success = false
        result.data = '发生异常'
        result.error = e
        event.reply('read-app-config-reply', result)
      }
    })

    // 写配置文件
    ipcMain.on('write-app-config', async (event, appConfigInfo) => {
      return
      console.log('=======写配置文件=======')
      console.log(appConfigInfo)
      if (appConfigInfo && appConfigInfo.deviceSerialNo && appConfigInfo.eipUrl) {
        var result = {
          success: false,
          data: '',
          error: ''
        }
        try {
          console.log(__dirname)
          fs.writeFile(path.join("C:\\nGSA\\", "data.json"), JSON.stringify(appConfigInfo), "utf8", (err) => {
            if (err) {
              result.success = false
              result.data = '写入失败'
              result.error = err
            } else {
              result.success = true
              result.data = appConfigInfo
            }
            event.reply('write-app-config-reply', result);
          })
        } catch (e) {
          result.success = false
          result.data = '发生异常'
          result.error = e
          event.reply('write-app-config-reply', result)
        }
      }
    })
    let mqttClient = null
    // connect MQTT
    ipcMain.on('start-mqtt-connect', async (event, arg) => {
      console.log('=======start-mqtt-connect=======')
      if (mqttClient && mqttClient.connected) {
        mqttClient.end()
      }
      mqttClient = mqtt.initMqtt(event, arg)
    })
    ipcMain.on('restart', (event, arg) => {
      mqttClient = null
    })
    // send MQTT message
    ipcMain.on('send-mqtt-client-message', async (event, url, arg) => {
      console.log('=======send-mqtt-client-message=======')
      console.log(arg)
      mqtt.sendMqttMessage(event, mqttClient, url, arg)
    })

    // send MQTT message
    ipcMain.on('get-client-type-message', async (event, arg) => {
      console.log('=======get-client-type-message=======')
      console.log(arg)
      mqtt.getClientType(event, mqttClient, arg)
    })

    ipcMain.on('close-mqtt-connect', async (event, arg) => {
      console.log('=======close-mqtt-connect=======')
      mqtt.closeConnect(event, mqttClient)
    })
    ipcMain.on('send-mqtt-client-check', async (event, arg) => {
      console.log('=======send-mqtt-client-check=======')
      if (!mqttClient || !mqttClient.connected) {
        if (mqttClient) {
          mqttClient.end()
        }
        event.reply('send-mqtt-client-check-reply', 501)
      } else {
        event.reply('send-mqtt-client-check-reply', 200)
      }
    })


    let childWin = null
    let cidArray = []
    ipcMain.handle('open-win', (event, arg) => {
      let cidJson = {
        id: null,
        url: ''
      }
      let data = cidArray.filter((currentValue) => {
        if (currentValue.url === arg.url) {
          return currentValue
        }
      })
      if (data.length > 0) {
        //获取当前窗口
        let currentWindow = BrowserWindow.fromId(data[0].id)
        //聚焦窗口
        currentWindow.focus()
      } else {
        //获取主窗口ID
        let parentID = event.sender.id
        //创建窗口
        childWin = new BrowserWindow({
          width: arg?.width || 842,
          height: arg?.height || 595,
          //width 和 height 将设置为 web 页面的尺寸(译注: 不包含边框), 这意味着窗口的实际尺寸将包括窗口边框的大小，稍微会大一点。
          useContentSize: true,
          //自动隐藏菜单栏，除非按了Alt键。
          autoHideMenuBar: true,
          //窗口大小是否可调整
          resizable: arg?.resizable ?? false,
          //窗口的最小高度
          minWidth: arg?.minWidth || 842,
          show: arg?.show ?? false,
          //窗口透明度
          opacity: arg?.opacity || 1.0,
          //当前窗口的父窗口ID
          parent: parentID,
          frame: IsUseSysTitle,
          webPreferences: {
            nodeIntegration: true,
            webSecurity: false,
            //使用webview标签 必须开启
            webviewTag: arg?.webview ?? false,
            // 如果是开发模式可以使用devTools
            // devTools: process.env.NODE_ENV === 'development',
            devTools: true,
            // 在macos中启用橡皮动画
            scrollBounce: process.platform === 'darwin',
            // 临时修复打开新窗口报错
            contextIsolation: false,
          },
        })
        childWin.loadURL(winURL + `#${arg.url}`)
        cidJson.id = childWin?.id
        cidJson.url = arg.url
        cidArray.push(cidJson)
        childWin.webContents.once('dom-ready', () => {
          childWin.show()
          childWin.webContents.send('send-data', arg.sendData)
          if (arg.IsPay) {
            // 检查支付时候自动关闭小窗口
            const testUrl = setInterval(() => {
              const Url = childWin.webContents.getURL()
              if (Url.includes(arg.PayUrl)) {
                childWin.close()
              }
            }, 1200)
            childWin.on('close', () => {
              clearInterval(testUrl)
            })
          }
        })
        childWin.on('closed', () => {
          childWin = null
          let index = cidArray.indexOf(cidJson)
          if (index > -1) {
            cidArray.splice(index, 1)
          }
        })
      }
    })
  },
}